import asyncio
from typing import Callable, Dict, Any

from fastapi import FastAPI
from typing import Callable

from starlette.background import BackgroundTask
from starlette.middleware.base import (BaseHTTPMiddleware, DispatchFunction,
                                       RequestResponseEndpoint)
from starlette.requests import Request
from starlette.responses import Response
from starlette.types import ASGIApp
from afast_core.core_plugins.pluginbase import IBasePlugin as BasePlugin
from afast_core.core_plugins.response_task.handel import SignalHandler
# 暂时存在问题，有待优化！！！！！！！！！
class ResponseTasksMiddleware(BaseHTTPMiddleware):
    """
    每个响应报文的都有一个可以执行的background任务
    定义响应报文的后台任务，但是这种定义反而先的复杂了！
    """

    def __init__(
            self, app: ASGIApp, dispatch: DispatchFunction = None, handler: Callable = None
    ) -> None:
        super().__init__(app, dispatch=dispatch)
        self.handler = handler

    async def dispatch(
            self, request: Request, call_next: RequestResponseEndpoint
    ) -> Response:
        request.state.background = None
        response = await call_next(request)
        # 后台任务必须存在的-
        if request.state.background:
            response.background = request.state.background
        return response


class SignalPluginClient(BasePlugin):
    '''
    示例：
    # # 后台任务放在里也可以执行！！！
    @SignalPluginClient.signal.register
    async def handler3(**kwargs):
        await asyncio.sleep(1)
        print(kwargs)
        print('Works3!')
    @core_app.get("/stream12")
    async def stream(request: Request,absk:BackgroundTasks):
        # 写入
        await SignalPluginClient.initiate_signal(request,'handler3',kkl='3')
        logger.info('aaaaa22222222222222---1')
        # 读取（另一个接口读取）
        # cyrewct_code = request.session["session_code"]
        return {
            "dasd": 2323
        }
    '''

    # 设置插件默认的参数信息
    name = 'Signal插件'
    signal = SignalHandler()

    @classmethod
    async def initiate_signal(cls, request: Request, name: str, **kwargs: Dict[str, Any]) -> None:
        task = BackgroundTask(cls.signal.handlers().get(name), **kwargs)
        request.state.background = task

    def setup(self, app: FastAPI, name: str = None, *args, **kwargs):
        """插件初始化"""
        app.add_middleware(ResponseTasksMiddleware)
